package tests;

import static org.junit.Assert.*;

import java.io.IOException;
import java.util.Iterator;

import org.junit.Before;
import org.junit.Test;

import peerToPeerFacebook.proj.Log;

public class LogTest
{
	protected MemoryStorage storage = null;
	
	@Before
	public void setUp() throws Exception
	{
		storage = new MemoryStorage();
	}

	@Test
	public void test() throws IOException
	{
		Log log = new Log(storage, "testFile");
		
		// Write some interesting stuff in
		log.writeStart("action1", null);
		log.writeEnd("action1");
		log.writeMark("mark1", "Hello world!");
		
		// Drop action that should be ignored.
		log.writeStart("action3", null);
		log.writeIgnore("action3");
		
		// leave one hanging writer
		log.writeStart("action2", "Hello universe!");
		
		// no read the stuff in
		Log l2 = new Log(storage, "testFile");
		Iterator<Log.LogRecord> records = l2.read().iterator();
		assertTrue("We should get first record", records.hasNext());
		
		Log.LogRecord record = records.next();
		assertEquals("First action", "action1", record.action);
		assertNull("Params", record.param);
		assertTrue("Record should be complete", record.completed);

		// Second
		assertTrue("We should get second record", records.hasNext());
		
		record = records.next();
		assertEquals("Second action", "mark1", record.action);
		assertEquals("Params", "Hello world!", record.param);
		assertTrue("Record should be complete", record.completed);

		// last record, that is not complete
		assertTrue("We should get third record", records.hasNext());
		
		record = records.next();
		assertEquals("Second action", "action2", record.action);
		assertEquals("Params", "Hello universe!", record.param);
		assertFalse("Record should NOT be complete", record.completed);
		
		assertFalse("We are done with records", records.hasNext());
	}
	
	@Test
	public void testMultipleWrites() throws IOException
	{
		Log log = new Log(storage, "testFile");
		log.writeStart("Action1", null);
	
		log = new Log(storage, "testFile");
		Iterator<Log.LogRecord> records = log.read().iterator();
		assertTrue(records.hasNext());
		
		Log.LogRecord record = records.next();
		assertEquals("Second action", "Action1", record.action);
		assertFalse("Record should be complete", record.completed);

		log.writeIgnore("Action1");
		
		// read back, we should have 0 elements
		log = new Log(storage, "testFile");
		records = log.read().iterator();
		assertFalse(records.hasNext());
		
		// Finally we should be able to write mark
		log.writeMark("Action2", null);
		
		// and read it back.
		log = new Log(storage, "testFile");
		records = log.read().iterator();
		assertTrue(records.hasNext());
		
		record = records.next();
		assertEquals("Action2", record.action);
		assertTrue(record.completed);

		// and nothing else
		assertFalse(records.hasNext());
	}
	
	@Test
	public void testReadEmptyLog() throws IOException
	{
		Log log = new Log(storage, "testFile");
		Iterator<Log.LogRecord> records = log.read().iterator();
		
		assertFalse(records.hasNext());
	}
}
